/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

/*
 * Cfg.java
 *
 * Created on 11.11.2009, 15:46:00
 */

package pabudr_se;

import java.awt.Color;
import java.awt.Dialog.ModalityType;
import java.awt.Dimension;
import java.util.ArrayList;
import javax.swing.JColorChooser;
import java.util.Date;
import java.util.Calendar;
import javax.swing.JDialog;
import javax.swing.JOptionPane;

/**
 *JPanel f√ºr die Konfiguration einer "Atomart"
 * @author Hendric Butz
 */
public class AtomCfgPanel extends javax.swing.JPanel {
    private static final boolean DEBUG = DebugStatus.DEBUG;
    final AtomPanel atomPanel;
    private Color jcc = Atom.DEFAULTCOLOR;
    private boolean configured = false;

    /**
     * Innere Klasse f√ºr werte der eingabe
     */
    static class CfgSettings
    {
        float speed, mass, radius, direction;
        int num;
        /**
         *
         * @return true wenn settings korrekt -> alle werte >= 0
         */
        boolean isValid()
        {
            return speed >= 0 && mass >= 0 && radius >= 0 && direction >= 0 && num >=0;
        }
    }
    
    //zur bestimmung des richtungsvektors aus, einer in grad angegebenen 
    // richtung und einer geschwindigkeit
    static class Direction
    {
        float vx, vy;
        Direction( float degree, float speed)
        {
            vy = (float) (Math.sin(degree) * speed);
            vx = (float) (Math.cos(degree) * speed);
        }

    }

    /** Creates new form Cfg */
    public AtomCfgPanel() {
        super();                
        this.atomPanel = AtomPanel.getAtomPanel();
        initComponents();
        color.setBackground(Atom.DEFAULTCOLOR);
        // STD-Werte -- ueber design gings net
        spNumber.setValue(1);

        // std Atomfarbe setzen
        
    }


    public void setAtomData(Atom a){
        if(a!=null){
            mass.setText(a.getMasse()+"");
            radius.setText(a.getRadius()+"");
            nam.setText(a.getName());
        }
    }

    /**
     *
     * @return bei korekter Eingabe settings sonst null
     */
    /*
     * ---- Wird nicht mehr gebraucht, das die einstellungspanele ein statisches
     * ---- AtomPanel selbst konfigurieren
    CfgSettings getCfgSettings() {
        final CfgSettings settings = new CfgSettings();
        try{
        settings.mass = Float.parseFloat(this.mass.getText().replace(',', '.'));
        settings.radius = Float.parseFloat(this.radius.getText().replace(',', '.'));
        settings.speed = Float.parseFloat(this.speed.getText().replace(',', '.'));
        settings.direction = Float.parseFloat(this.direction.getText().replace(',', '.'));
        }catch( NumberFormatException e)
        {
            e.printStackTrace();
            return null;
        }

        return (settings.isValid()) ? settings : null;
    }*/



    /** This method is called from within the constructor to
     * initialize the form.
     * WARNING: Do NOT modify this code. The content of this method is
     * always regenerated by the Form Editor.
     */
    @SuppressWarnings("unchecked")
    // <editor-fold defaultstate="collapsed" desc="Generated Code">//GEN-BEGIN:initComponents
    private void initComponents() {

        jPanel1 = new javax.swing.JPanel();
        jLabel1 = new javax.swing.JLabel();
        jLabel2 = new javax.swing.JLabel();
        jLabel3 = new javax.swing.JLabel();
        jLabel4 = new javax.swing.JLabel();
        speed = new javax.swing.JTextField();
        mass = new javax.swing.JTextField();
        radius = new javax.swing.JTextField();
        buPeriodicTable = new javax.swing.JButton();
        jLabel6 = new javax.swing.JLabel();
        nam = new javax.swing.JTextField();
        jLabel7 = new javax.swing.JLabel();
        spNumber = new javax.swing.JSpinner();
        jLabel8 = new javax.swing.JLabel();
        jButton1 = new javax.swing.JButton();
        color = new javax.swing.JPanel();

        jPanel1.setName("jPanel1"); // NOI18N

        javax.swing.GroupLayout jPanel1Layout = new javax.swing.GroupLayout(jPanel1);
        jPanel1.setLayout(jPanel1Layout);
        jPanel1Layout.setHorizontalGroup(
            jPanel1Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGap(0, 100, Short.MAX_VALUE)
        );
        jPanel1Layout.setVerticalGroup(
            jPanel1Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGap(0, 100, Short.MAX_VALUE)
        );

        setBorder(javax.swing.BorderFactory.createLineBorder(new java.awt.Color(0, 0, 0)));
        setName("Form"); // NOI18N

        org.jdesktop.application.ResourceMap resourceMap = org.jdesktop.application.Application.getInstance().getContext().getResourceMap(AtomCfgPanel.class);
        jLabel1.setText(resourceMap.getString("jLabel1.text")); // NOI18N
        jLabel1.setName("jLabel1"); // NOI18N

        jLabel2.setText(resourceMap.getString("jLabel2.text")); // NOI18N
        jLabel2.setName("jLabel2"); // NOI18N

        jLabel3.setText(resourceMap.getString("jLabel3.text")); // NOI18N
        jLabel3.setName("jLabel3"); // NOI18N

        jLabel4.setText(resourceMap.getString("jLabel4.text")); // NOI18N
        jLabel4.setName("jLabel4"); // NOI18N

        speed.setHorizontalAlignment(javax.swing.JTextField.TRAILING);
        speed.setText(resourceMap.getString("speed.text")); // NOI18N
        speed.setToolTipText(resourceMap.getString("speed.toolTipText")); // NOI18N
        speed.setName("speed"); // NOI18N
        speed.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                speedActionPerformed(evt);
            }
        });

        mass.setHorizontalAlignment(javax.swing.JTextField.TRAILING);
        mass.setText(resourceMap.getString("mass.text")); // NOI18N
        mass.setToolTipText(resourceMap.getString("mass.toolTipText")); // NOI18N
        mass.setName("mass"); // NOI18N
        mass.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                massActionPerformed(evt);
            }
        });

        radius.setHorizontalAlignment(javax.swing.JTextField.TRAILING);
        radius.setText(resourceMap.getString("radius.text")); // NOI18N
        radius.setToolTipText(resourceMap.getString("radius.toolTipText")); // NOI18N
        radius.setName("radius"); // NOI18N

        buPeriodicTable.setText(resourceMap.getString("buPeriodicTable.text")); // NOI18N
        buPeriodicTable.setToolTipText(resourceMap.getString("buPeriodicTable.toolTipText")); // NOI18N
        buPeriodicTable.setName("buPeriodicTable"); // NOI18N
        buPeriodicTable.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                buPeriodicTableActionPerformed(evt);
            }
        });

        jLabel6.setName("jLabel6"); // NOI18N

        nam.setText(resourceMap.getString("nam.text")); // NOI18N
        nam.setHorizontalAlignment(javax.swing.JTextField.TRAILING);
        nam.setToolTipText(resourceMap.getString("nam.toolTipText")); // NOI18N
        nam.setName("nam"); // NOI18N

        jLabel7.setText(resourceMap.getString("jLabel7.text")); // NOI18N
        jLabel7.setName("jLabel7"); // NOI18N

        spNumber.setToolTipText(resourceMap.getString("spNumber.toolTipText")); // NOI18N
        spNumber.setName("spNumber"); // NOI18N

        jLabel8.setText(resourceMap.getString("jLabel8.text")); // NOI18N
        jLabel8.setName("jLabel8"); // NOI18N

        jButton1.setText(resourceMap.getString("jButton1.text")); // NOI18N
        jButton1.setToolTipText(resourceMap.getString("jButton1.toolTipText")); // NOI18N
        jButton1.setName("jButton1"); // NOI18N
        jButton1.addActionListener(new java.awt.event.ActionListener() {
            public void actionPerformed(java.awt.event.ActionEvent evt) {
                jButton1ActionPerformed(evt);
            }
        });

        color.setToolTipText(resourceMap.getString("color.toolTipText")); // NOI18N
        color.setName("color"); // NOI18N
        color.addMouseListener(new java.awt.event.MouseAdapter() {
            public void mouseClicked(java.awt.event.MouseEvent evt) {
                colorMouseClicked(evt);
            }
        });

        javax.swing.GroupLayout colorLayout = new javax.swing.GroupLayout(color);
        color.setLayout(colorLayout);
        colorLayout.setHorizontalGroup(
            colorLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGap(0, 147, Short.MAX_VALUE)
        );
        colorLayout.setVerticalGroup(
            colorLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGap(0, 24, Short.MAX_VALUE)
        );

        javax.swing.GroupLayout layout = new javax.swing.GroupLayout(this);
        this.setLayout(layout);
        layout.setHorizontalGroup(
            layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGroup(layout.createSequentialGroup()
                .addContainerGap()
                .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                    .addGroup(layout.createSequentialGroup()
                        .addComponent(jLabel6)
                        .addGap(16, 16, 16))
                    .addGroup(layout.createSequentialGroup()
                        .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                            .addGroup(layout.createSequentialGroup()
                                .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                                    .addGroup(layout.createSequentialGroup()
                                        .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                                            .addComponent(jLabel4)
                                            .addComponent(jLabel7)
                                            .addComponent(jLabel8))
                                        .addGap(54, 54, 54)
                                        .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                                            .addComponent(spNumber, javax.swing.GroupLayout.DEFAULT_SIZE, 199, Short.MAX_VALUE)
                                            .addComponent(color, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
                                            .addComponent(nam, javax.swing.GroupLayout.DEFAULT_SIZE, 199, Short.MAX_VALUE)))
                                    .addGroup(javax.swing.GroupLayout.Alignment.TRAILING, layout.createSequentialGroup()
                                        .addGap(2, 2, 2)
                                        .addComponent(jButton1)
                                        .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED)
                                        .addComponent(buPeriodicTable, javax.swing.GroupLayout.DEFAULT_SIZE, 177, Short.MAX_VALUE)))
                                .addGap(6, 6, 6))
                            .addGroup(javax.swing.GroupLayout.Alignment.TRAILING, layout.createSequentialGroup()
                                .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                                    .addComponent(jLabel3)
                                    .addComponent(jLabel1)
                                    .addComponent(jLabel2))
                                .addGap(59, 59, 59)
                                .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
                                    .addComponent(radius, javax.swing.GroupLayout.Alignment.TRAILING, javax.swing.GroupLayout.DEFAULT_SIZE, 208, Short.MAX_VALUE)
                                    .addComponent(mass, javax.swing.GroupLayout.Alignment.TRAILING, javax.swing.GroupLayout.DEFAULT_SIZE, 208, Short.MAX_VALUE)
                                    .addComponent(speed, javax.swing.GroupLayout.Alignment.TRAILING, javax.swing.GroupLayout.DEFAULT_SIZE, 208, Short.MAX_VALUE))))
                        .addContainerGap())))
        );
        layout.setVerticalGroup(
            layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGroup(javax.swing.GroupLayout.Alignment.TRAILING, layout.createSequentialGroup()
                .addContainerGap()
                .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
                    .addComponent(jLabel1)
                    .addComponent(speed, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE))
                .addGap(18, 18, 18)
                .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
                    .addComponent(jLabel2)
                    .addComponent(mass, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE))
                .addGap(18, 18, 18)
                .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
                    .addComponent(jLabel3)
                    .addComponent(radius, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE))
                .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED)
                .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
                    .addComponent(jLabel4)
                    .addComponent(spNumber, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE))
                .addGap(18, 18, 18)
                .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
                    .addComponent(nam, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE)
                    .addComponent(jLabel7))
                .addGap(11, 11, 11)
                .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.TRAILING)
                    .addComponent(jLabel8)
                    .addComponent(color, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE))
                .addGap(43, 43, 43)
                .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE)
                    .addComponent(buPeriodicTable, javax.swing.GroupLayout.PREFERRED_SIZE, 23, javax.swing.GroupLayout.PREFERRED_SIZE)
                    .addComponent(jButton1))
                .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED, 7, Short.MAX_VALUE)
                .addComponent(jLabel6)
                .addGap(77, 77, 77))
        );
    }// </editor-fold>//GEN-END:initComponents

    private void massActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_massActionPerformed
        System.out.println("Mass action");
    }//GEN-LAST:event_massActionPerformed

    private void speedActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_speedActionPerformed
        System.out.println("Speed action");
    }//GEN-LAST:event_speedActionPerformed

    private void buPeriodicTableActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_buPeriodicTableActionPerformed
        PeriodicTable pt = new PeriodicTable(null, true, this);
        pt.setLocationRelativeTo(this);
        pt.setVisible(true);
    }//GEN-LAST:event_buPeriodicTableActionPerformed


    // Add-Atom Button aus der Bedienoeberflaeche
    private void jButton1ActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_jButton1ActionPerformed

        

        final float lSpeed, lMass, rad;
        final int addCount;
        try {
            lSpeed = this.getSpeed();
            lMass = this.getMass();
            rad = this.getRadius();
            addCount = this.getNumber();
        if (addCount <= 0 || lSpeed < 0 || lMass < 0|| rad < 0)
            throw new NumberFormatException();
        }

        catch (NumberFormatException e)
        {
            JOptionPane.showMessageDialog(JOptionPane.getRootFrame(), "Input Error.");
            return;
        }

        // wurde einmal eine atomkonfiguration festgelegt, nicht mehr aenderbar
        // nur weiteres hinzufuegen moeglich
            if(!configured) setConfigured(true);          


        // atom liste fuer eine configuration erstellen
        Dimension panelDim = atomPanel.getSize();

        if(DEBUG)
        {
            System.out.println("Atome mit Default startpunkt erzeugen");
        }

        final Simulator sim = new Simulator(atomPanel);

        int tryCount = 0;

        //final long timeBefore = Calendar.getInstance().getTimeInMillis();
        //if (DEBUG) System.out.println("timeBefore" + timeBefore);
        for( int i = 0; i < this.getNumber(); ++i )
        {
            ++tryCount;
            //final long timeAfter = Calendar.getInstance().getTimeInMillis();
            //if (DEBUG) System.out.println("timeAfter" + timeAfter);
            //warte maximal 2 sekunden
            //if (timeAfter - timeBefore > 2000)
            if (tryCount > addCount * 10)
            {
                JOptionPane.showMessageDialog(JOptionPane.getRootFrame(), "Too many Atoms");
                break;
            }
            final float x = ((float)Math.random() * (panelDim.width - 4*rad)) + 2*rad;
            final float y = ((float)Math.random() * (panelDim.height - 4*rad)) + 2*rad;
            final Direction atomDirection = new Direction((float)Math.random() * 360, lSpeed);
            final Atom a = new Atom(x, y, atomDirection.vx, atomDirection.vy, lMass, rad, this.getColor());
            
            //Pruefe ob schon eine Kollision verliegt
            if (sim.atomkollision(a, true))
            {
                --i;
                continue;
            }
            for (Barrier b : atomPanel.getList_barrieren())
            {
                if (sim.barrierAtomIntersect(a, b))
                {
                    --i;
                    continue;
                }
            }

            //Atom kann gefahrlos hinzugefuegt werden
            sim.list_atome.add(a);
        }

        // Settings der aktuell angezeigten Atome/Barrieren holen
        Settings set = atomPanel.getSettings();

        // neue atomauswahl wird aus der liste der angezeigten geloescht
        // vermeidet fehler durch doppelbesetzungen
        //set.list_atome.removeAll(atomList);
        
        // Neue Atomauswahl zur anzeige hinzufuegen
        //set.list_atome.addAll(atomList);

        // settings neu schreiben
        //atomPanel.setSettings(set);
        
        //neue liste auf panel malen
        atomPanel.repaint();

    }//GEN-LAST:event_jButton1ActionPerformed

    private void colorMouseClicked(java.awt.event.MouseEvent evt) {//GEN-FIRST:event_colorMouseClicked
       jcc = JColorChooser.showDialog(null, "Color Chooser", Atom.DEFAULTCOLOR);
        color.setBackground(jcc);
    }//GEN-LAST:event_colorMouseClicked

    public float getSpeed(){
        return Float.parseFloat(speed.getText());
    }

    public float getMass(){
        return Float.parseFloat(mass.getText())/10;
    }

    public float getRadius(){
        return Float.parseFloat(radius.getText())/10;
    }

    public int getNumber(){
        return (Integer)spNumber.getValue();
    }

    public String getName(){
        return nam.getText();
    }

    public Color getColor(){
        return jcc;
    }

    private void setConfigured(final boolean b)
    {
        //Zustand der konfiguration aendern
        this.configured = b;

        // wenn true, elemente deaktivieren
        // sonst aktivieren
        final boolean cfg = !this.configured;
        //atomPanel.invalidate();
        speed.setEnabled(cfg);
        speed.setEnabled(cfg);
        mass.setEnabled(cfg);
        nam.setEnabled(cfg);
        radius.setEnabled(cfg);
        color.setEnabled(cfg);
        buPeriodicTable.setEnabled(cfg);
        //atomPanel.validate();
        //atomPanel.repaint();
    }
    
    /**
     * Wenn gesperrte teile von AtomCfgPanels von aussen wieder entsperrt wurden
     * setzt diese methode die panels auf den zustand vor der verstellung zurueck
     * 
     * @param acp
     */
    public static void allowAtomConfiguration(AtomCfgPanel ... acp)
    {
        for(int i = 0; i < acp.length; i++) acp[i].setConfigured(acp[i].configured);
    }

    ArrayList<Atom> atomList;

    // Variables declaration - do not modify//GEN-BEGIN:variables
    private javax.swing.JButton buPeriodicTable;
    private javax.swing.JPanel color;
    private javax.swing.JButton jButton1;
    private javax.swing.JLabel jLabel1;
    private javax.swing.JLabel jLabel2;
    private javax.swing.JLabel jLabel3;
    private javax.swing.JLabel jLabel4;
    private javax.swing.JLabel jLabel6;
    private javax.swing.JLabel jLabel7;
    private javax.swing.JLabel jLabel8;
    private javax.swing.JPanel jPanel1;
    private javax.swing.JTextField mass;
    private javax.swing.JTextField nam;
    private javax.swing.JTextField radius;
    private javax.swing.JSpinner spNumber;
    private javax.swing.JTextField speed;
    // End of variables declaration//GEN-END:variables

}
